package cn.lblbc.appassit

import android.content.Intent
import android.net.Uri
import android.os.Build
import android.os.Bundle
import android.os.Environment
import android.os.Handler
import android.os.Looper
import android.text.Editable
import android.text.TextWatcher
import android.util.Log
import android.view.Menu
import android.view.MenuItem
import android.view.View
import android.widget.ProgressBar
import android.widget.TextView
import android.widget.Toast
import android.widget.CompoundButton
import androidx.activity.OnBackPressedCallback
import androidx.activity.result.contract.ActivityResultContracts
import androidx.appcompat.app.AlertDialog
import androidx.appcompat.app.AppCompatActivity
import androidx.lifecycle.lifecycleScope
import cn.lblbc.appassit.databinding.ActivityMainBinding
import cn.lblbc.appassit.fragment.AppListFragment
import cn.lblbc.appassit.model.AppInfo
import cn.lblbc.appassit.utils.AppExporter
import cn.lblbc.appassit.utils.AppScanner
import cn.lblbc.appassit.utils.ExportResultDialogHelper
import cn.lblbc.appassit.utils.FileNameInputDialog
import cn.lblbc.appassit.utils.FileUtils
import cn.lblbc.appassit.utils.PermissionHelper
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch
import kotlinx.coroutines.withContext

private const val TAG = "MainActivityPerf"

class MainActivity : AppCompatActivity() {

    private lateinit var binding: ActivityMainBinding
    private lateinit var appScanner: AppScanner
    private lateinit var appExporter: AppExporter
    private lateinit var appListFragment: AppListFragment
    private lateinit var exportResultDialogHelper: ExportResultDialogHelper
    private lateinit var fileNameInputDialog: FileNameInputDialog

    private var allApps = listOf<AppInfo>()
    private var showSystemApps = false
    // 新增一个变量，用于标记系统应用是否已加载
    private var systemAppsLoaded = false

    // 存储权限回调
    private var permissionCallback: ((Boolean) -> Unit)? = null
    
    // 权限请求
    private val storagePermissionLauncher = registerForActivityResult(
        ActivityResultContracts.RequestMultiplePermissions()
    ) { permissions ->
        val allGranted = permissions.values.all { it }
        permissionCallback?.invoke(allGranted) ?: run {
            // 如果没有设置回调，使用默认行为
            if (allGranted) {
                loadApps()
            } else {
                showPermissionDeniedDialog()
            }
        }
        permissionCallback = null
    }

    // Android 11+ 管理外部存储权限
    private val manageStorageLauncher = registerForActivityResult(
        ActivityResultContracts.StartActivityForResult()
    ) {
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
            val granted = Environment.isExternalStorageManager()
            permissionCallback?.invoke(granted) ?: run {
                // 如果没有设置回调，使用默认行为
                if (granted) {
                    loadApps()
                } else {
                    showPermissionDeniedDialog()
                }
            }
            permissionCallback = null
        }
    }

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        binding = ActivityMainBinding.inflate(layoutInflater)
        setContentView(binding.root)

        initializeComponents()
        setupUI()
        setupBackPressedCallback()
        loadApps() // 直接加载应用，不检查权限
    }

    private fun initializeComponents() {
        appScanner = AppScanner(this)
        appExporter = AppExporter(this)
        exportResultDialogHelper = ExportResultDialogHelper(this)
        fileNameInputDialog = FileNameInputDialog(this)

        // 创建应用列表Fragment
        appListFragment = AppListFragment.newInstance()

        // 将Fragment添加到容器中
        supportFragmentManager.beginTransaction()
            .replace(binding.flAppListContainer.id, appListFragment)
            .commit()
    }

    // 复选框监听器
    private val checkBoxListener = CompoundButton.OnCheckedChangeListener { _, isChecked ->
        if (isChecked) {
            appListFragment.selectAll()
        } else {
            appListFragment.clearSelection()
        }
        updateSelectionUI()
    }

    private fun setupUI() {
        setSupportActionBar(binding.toolbar)

        // 设置搜索监听器
        binding.etSearch.addTextChangedListener(object : TextWatcher {
            override fun beforeTextChanged(s: CharSequence?, start: Int, count: Int, after: Int) {}

            override fun onTextChanged(s: CharSequence?, start: Int, before: Int, count: Int) {}

            override fun afterTextChanged(s: Editable?) {
                val query = s?.toString() ?: ""
                performSearch(query)
            }
        })

        // 底部操作栏按钮
        // 设置复选框监听器
        binding.cbSelectAll.setOnCheckedChangeListener(checkBoxListener)

        binding.btnExport.setOnClickListener {
            exportSelectedApps()
        }

        binding.btnUninstall.setOnClickListener {
            uninstallSelectedApps()
        }
    }

    override fun onCreateOptionsMenu(menu: Menu): Boolean {
        menuInflater.inflate(R.menu.menu_main, menu)
        // 设置"显示系统应用"菜单项的初始状态
        val showSystemAppsItem = menu.findItem(R.id.action_show_system_apps)
        showSystemAppsItem.isChecked = showSystemApps
        return true
    }

    override fun onOptionsItemSelected(item: MenuItem): Boolean {
        return when (item.itemId) {
            R.id.action_show_system_apps -> {
                showSystemApps = !showSystemApps
                item.isChecked = showSystemApps
                
                // 如果需要显示系统应用且尚未加载，则加载系统应用
                if (showSystemApps && !systemAppsLoaded) {
                    loadSystemApps()
                } else {
                    // 否则直接更新应用列表
                    updateAppListFragment()
                }
                true
            }

            R.id.action_settings -> {
                openSettings()
                true
            }

            else -> super.onOptionsItemSelected(item)
        }
    }

    private fun openSettings() {
        val intent = Intent(this, SettingsActivity::class.java)
        startActivity(intent)
    }

    private fun setupBackPressedCallback() {
        onBackPressedDispatcher.addCallback(this, object : OnBackPressedCallback(true) {
            override fun handleOnBackPressed() {
                // 如果当前在选择模式，退出选择模式
                if (appListFragment.getSelectedCount() > 0) {
                    exitSelectionMode()
                } else {
                    // 否则直接退出应用
                    finish()
                }
            }
        })
    }

    // 移除启动时的权限检查，改为在需要时才检查权限

    private fun showPermissionDeniedDialog() {
        AlertDialog.Builder(this)
            .setTitle(R.string.permission_storage_title)
            .setMessage(R.string.permission_storage_message)
            .setPositiveButton("设置") { _, _ ->
                requestStoragePermissions { granted ->
                    if (granted) {
                        loadApps()
                    } else {
                        showPermissionDeniedDialog()
                    }
                }
            }
            .setNegativeButton("取消") { _, _ ->
                finish()
            }
            .show()
    }

    private fun loadApps() {
        loadApps(true)
    }

    private fun loadApps(showProgressBar: Boolean) {
        val startTime = System.currentTimeMillis()
        Log.d(TAG, "开始加载应用列表，showProgressBar=$showProgressBar")

        if (showProgressBar) {
            binding.progressBar.visibility = View.VISIBLE
        }

        // 显示加载状态文本
        binding.tvLoadingStatus.text = "正在扫描应用..."
        binding.tvLoadingStatus.visibility = View.VISIBLE

        lifecycleScope.launch {
            try {
                val scanStart = System.currentTimeMillis()
                // 首次加载只加载用户应用，不加载系统应用
                allApps = withContext(Dispatchers.IO) {
                    appScanner.scanInstalledApps(false) // 只获取用户应用
                }
                systemAppsLoaded = false // 系统应用尚未加载
                Log.d(TAG, "扫描应用完成，耗时${System.currentTimeMillis() - scanStart}ms, 共${allApps.size}个应用")

                // 更新Fragment
                val fragmentUpdateStart = System.currentTimeMillis()
                updateAppListFragment()
                Log.d(TAG, "更新Fragment完成，耗时${System.currentTimeMillis() - fragmentUpdateStart}ms")

                // 如果应用数量很少，提示用户可能需要权限
                if (allApps.size < 10) {
                    showQueryPermissionHint()
                }

                // 加载完成后隐藏加载状态文本
                binding.tvLoadingStatus.visibility = View.GONE

            } catch (e: SecurityException) {
                showQueryPermissionDialog()
                Log.e(TAG, "安全权限异常: ${e.message}")
            } catch (e: Exception) {
                Toast.makeText(this@MainActivity, "加载应用失败: ${e.message}", Toast.LENGTH_SHORT).show()
                Log.e(TAG, "加载应用失败: ${e.message}", e)
            } finally {
                if (showProgressBar) {
                    binding.progressBar.visibility = View.GONE
                }
                Log.d(TAG, "加载应用列表完整流程完成，总耗时${System.currentTimeMillis() - startTime}ms")
            }
        }
    }

    // 新增方法：加载系统应用
    private fun loadSystemApps() {
        binding.progressBar.visibility = View.VISIBLE
        binding.tvLoadingStatus.text = "正在加载系统应用..."
        binding.tvLoadingStatus.visibility = View.VISIBLE

        lifecycleScope.launch {
            try {
                val scanStart = System.currentTimeMillis()
                val systemApps = withContext(Dispatchers.IO) {
                    appScanner.scanInstalledApps(true) // 获取所有应用
                }
                allApps = systemApps
                systemAppsLoaded = true // 标记系统应用已加载
                Log.d(TAG, "加载系统应用完成，耗时${System.currentTimeMillis() - scanStart}ms")

                updateAppListFragment()

            } catch (e: SecurityException) {
                showQueryPermissionDialog()
                Log.e(TAG, "安全权限异常: ${e.message}")
            } catch (e: Exception) {
                Toast.makeText(this@MainActivity, "加载系统应用失败: ${e.message}", Toast.LENGTH_SHORT).show()
                Log.e(TAG, "加载系统应用失败: ${e.message}", e)
            } finally {
                binding.progressBar.visibility = View.GONE
                binding.tvLoadingStatus.visibility = View.GONE
            }
        }
    }

    private fun updateAppListFragment() {
        val uiUpdateStart = System.currentTimeMillis()

        // 确保在主线程上执行UI更新
        if (Looper.myLooper() != Looper.getMainLooper()) {
            Log.w(TAG, "updateAppListFragment: 在非主线程上调用，切换到主线程")
            runOnUiThread {
                internalUpdateAppListFragment()
            }
            return
        }

        internalUpdateAppListFragment()

        Log.d(TAG, "UI更新操作完成，耗时${System.currentTimeMillis() - uiUpdateStart}ms")
    }

    // 内部方法，确保在主线程上被调用
    private fun internalUpdateAppListFragment() {
        // 根据showSystemApps标志决定显示哪些应用
        val filterStart = System.currentTimeMillis()
        val appsToShow = if (showSystemApps) {
            allApps
        } else {
            // 优化：预计算过滤结果并缓存，避免重复过滤
            allApps.filter { !it.isSystemApp }
        }
        Log.d(TAG, "过滤应用列表耗时${System.currentTimeMillis() - filterStart}ms, 过滤后${appsToShow.size}个应用")

        // 更新Fragment中的应用列表
        val listUpdateStart = System.currentTimeMillis()
        appListFragment.updateAppList(appsToShow)
        Log.d(TAG, "更新Fragment列表耗时${System.currentTimeMillis() - listUpdateStart}ms")

        // 设置监听器
        appListFragment.setOnAppClickListener { appInfo ->
            showAppDetailsDialog(appInfo)
        }

        appListFragment.setOnRefreshListener {
            loadApps(false)
        }

        appListFragment.setOnSelectionChangedListener {
            updateSelectionUI()
        }

        appListFragment.setOnExportClickListener { appInfo ->
            exportSingleApp(appInfo)
        }

        appListFragment.setOnOpenClickListener { appInfo ->
            openApp(appInfo.packageName)
        }

        // 应用当前搜索查询
        val currentQuery = binding.etSearch.text?.toString() ?: ""
        if (currentQuery.isNotBlank()) {
            performSearch(currentQuery)
        }

        // 更新统计信息
        updateStatsUI()
    }

    private fun showQueryPermissionDialog() {
        AlertDialog.Builder(this)
            .setTitle(R.string.query_packages_permission_title)
            .setMessage(R.string.query_packages_permission_message)
            .setPositiveButton("了解") { _, _ ->
                Toast.makeText(this, R.string.permission_query_denied, Toast.LENGTH_LONG).show()
            }
            .setNegativeButton("重试") { _, _ ->
                loadApps()
            }
            .show()
    }

    private fun showQueryPermissionHint() {
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
            Toast.makeText(
                this,
                "提示：如果应用列表不完整，可能需要在应用信息中授予\"查询所有应用包\"权限",
                Toast.LENGTH_LONG
            ).show()
        }
    }

    private fun updateStatsUI() {
        val appCount = appListFragment.getAppCount()
        val totalAppCount = appListFragment.getTotalAppCount()

        val searchQuery = binding.etSearch.text?.toString() ?: ""
        if (searchQuery.isNotBlank()) {
            // 更新标题（搜索结果）
            supportActionBar?.title = "应用列表 ($appCount)"
        } else {
            // 更新标题（总数量）
            supportActionBar?.title = "应用列表 ($totalAppCount)"
        }
    }

    private fun performSearch(query: String) {
        appListFragment.searchApps(query)
        updateStatsUI()
    }

    private fun updateSelectionUI() {
        val selectedCount = appListFragment.getSelectedCount()

        // 只有在有选中的应用时才显示底部操作栏
        if (selectedCount > 0) {
            binding.llBottomActions.visibility = View.VISIBLE
        } else {
            binding.llBottomActions.visibility = View.GONE
        }

        // 更新复选框状态和文本
        val totalApps = appListFragment.getAppCount()
        // 移除监听器以避免循环调用
        binding.cbSelectAll.setOnCheckedChangeListener(null)
        binding.cbSelectAll.isChecked = totalApps > 0 && selectedCount == totalApps
        // 更新复选框文本为已选数量
        binding.cbSelectAll.text = "$selectedCount/$totalApps"
        // 重新设置监听器（使用预先定义的监听器对象）
        binding.cbSelectAll.setOnCheckedChangeListener(checkBoxListener)

        // 使用Handler延迟设置选择模式，避免RecyclerView计算布局或滚动时调用
        Handler(Looper.getMainLooper()).post {
            // 只有在没有选中的应用时才退出选择模式
            // 这样可以防止长按时选择模式被意外关闭
            if (selectedCount == 0) {
                appListFragment.setSelectionMode(false)
            }
            // 如果有选中的应用，确保选择模式是开启的
            else if (!appListFragment.getSelectedApps().isEmpty()) {
                appListFragment.setSelectionMode(true)
            }
        }
    }

    private fun getTotalSelectedCount(): Int {
        return appListFragment.getSelectedCount()
    }

    private fun getAllSelectedApps(): List<AppInfo> {
        return appListFragment.getSelectedApps()
    }

    private fun exitSelectionMode() {
        // 隐藏底部操作栏
        binding.llBottomActions.visibility = View.GONE

        // 使用Handler延迟设置选择模式，避免RecyclerView计算布局或滚动时调用
        Handler(Looper.getMainLooper()).post {
            // 更新Fragment的选择模式
            appListFragment.setSelectionMode(false)
            // 清除所有已选中的应用
            appListFragment.clearSelection()
        }
    }

    private fun exportSelectedApps() {
        val selectedApps = getAllSelectedApps()
        if (selectedApps.isEmpty()) {
            Toast.makeText(this, R.string.no_apps_selected, Toast.LENGTH_SHORT).show()
            return
        }

        // 检查权限
        if (!PermissionHelper.hasStoragePermissions(this)) {
            // 显示权限说明弹窗
            androidx.appcompat.app.AlertDialog.Builder(this)
                .setTitle(R.string.permission_storage_title)
                .setMessage("需要存储权限来导出应用文件。\n\n授予权限后，您可以将应用导出到指定目录。")
                .setPositiveButton("授予权限") { _, _ ->
                    requestStoragePermissions { granted ->
                        if (granted) {
                            val exportDir = FileUtils.getExportDirectory(this)
                            performExport(selectedApps, exportDir)
                        } else {
                            Toast.makeText(this, "需要存储权限才能导出应用", Toast.LENGTH_SHORT).show()
                        }
                    }
                }
                .setNegativeButton("取消", null)
                .show()
            return
        }

        val exportDir = FileUtils.getExportDirectory(this)
        performExport(selectedApps, exportDir)
    }
    
    private fun requestStoragePermissions(callback: (Boolean) -> Unit) {
        // 设置回调
        permissionCallback = callback
        
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
            val intent = PermissionHelper.getStoragePermissionIntent(this)
            manageStorageLauncher.launch(intent)
        } else {
            val permissions = PermissionHelper.getRequiredPermissions()
            if (permissions.isNotEmpty()) {
                storagePermissionLauncher.launch(permissions)
            } else {
                callback(true)
            }
        }
    }

    private fun performExport(selectedApps: List<AppInfo>, exportDir: String) {
        // 检查存储空间
        if (!FileUtils.isExternalStorageWritable()) {
            Toast.makeText(this, "外部存储不可写", Toast.LENGTH_SHORT).show()
            return
        }

        val availableSpace = FileUtils.getAvailableStorageSpace()
        val estimatedSize = selectedApps.sumOf { it.apkSize }

        if (availableSpace < estimatedSize) {
            AlertDialog.Builder(this)
                .setTitle("存储空间不足")
                .setMessage("可用空间: ${FileUtils.formatFileSize(availableSpace)}\n需要空间: ${FileUtils.formatFileSize(estimatedSize)}")
                .setPositiveButton("确定", null)
                .show()
            return
        }

        // 显示导出进度对话框
        val progressDialog = createExportProgressDialog(selectedApps.size)
        progressDialog.show()

        lifecycleScope.launch {
            try {
                val result = appExporter.exportApps(selectedApps, exportDir)

                progressDialog.dismiss()
                showExportResultDialog(result)

            } catch (e: Exception) {
                progressDialog.dismiss()
                Toast.makeText(this@MainActivity, "导出失败: ${e.message}", Toast.LENGTH_LONG).show()
            }
        }
    }

    private fun createExportProgressDialog(totalCount: Int): AlertDialog {
        val dialogView = layoutInflater.inflate(R.layout.dialog_export_progress, null)
        val progressBar = dialogView.findViewById<ProgressBar>(R.id.progress_bar)
        val progressText = dialogView.findViewById<TextView>(R.id.tv_progress_text)

        progressBar.max = totalCount
        progressText.text = "准备导出..."

        return AlertDialog.Builder(this)
            .setView(dialogView)
            .setCancelable(false)
            .create()
    }

    private fun showExportResultDialog(result: AppExporter.ExportResult) {
        exportResultDialogHelper.showExportResultDialog(result)
    }

    private fun showAppDetailsDialog(appInfo: AppInfo) {
        // 启动应用详情Activity，使用startActivityForResult以便接收卸载结果
        val intent = Intent(this, AppDetailActivity::class.java)
        intent.putExtra("app_info", appInfo)
        startActivityForResult(intent, REQUEST_APP_DETAIL)
    }
    
    override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
        super.onActivityResult(requestCode, resultCode, data)
        if (requestCode == REQUEST_APP_DETAIL && resultCode == RESULT_OK) {
            // 应用被卸载，刷新应用列表
            loadApps(false) // 不显示进度条
        }
    }
    
    companion object {
        private const val REQUEST_APP_DETAIL = 1001
    }

    private fun openApp(packageName: String) {
        try {
            val intent = packageManager.getLaunchIntentForPackage(packageName)
            if (intent != null) {
                startActivity(intent)
            } else {
                Toast.makeText(this, "无法启动该应用", Toast.LENGTH_SHORT).show()
            }
        } catch (e: Exception) {
            Toast.makeText(this, "启动应用失败", Toast.LENGTH_SHORT).show()
        }
    }

    private fun exportSingleApp(appInfo: AppInfo) {
        // 检查存储空间
        if (!FileUtils.isExternalStorageWritable()) {
            Toast.makeText(this, "外部存储不可写", Toast.LENGTH_SHORT).show()
            return
        }

        val exportDir = FileUtils.getExportDirectory(this)
        val availableSpace = FileUtils.getAvailableStorageSpace()

        if (availableSpace < appInfo.apkSize) {
            Toast.makeText(this, "存储空间不足", Toast.LENGTH_SHORT).show()
            return
        }

        // 检查权限
        if (!PermissionHelper.hasStoragePermissions(this)) {
            // 显示权限说明弹窗
            androidx.appcompat.app.AlertDialog.Builder(this)
                .setTitle(R.string.permission_storage_title)
                .setMessage("需要存储权限来导出应用文件。\n\n授予权限后，您可以将应用导出到指定目录。")
                .setPositiveButton("授予权限") { _, _ ->
                    requestStoragePermissions { granted ->
                        if (granted) {
                            proceedWithSingleAppExport(appInfo, exportDir)
                        } else {
                            Toast.makeText(this, "需要存储权限才能导出应用", Toast.LENGTH_SHORT).show()
                        }
                    }
                }
                .setNegativeButton("取消", null)
                .show()
            return
        }

        proceedWithSingleAppExport(appInfo, exportDir)
    }
    
    private fun proceedWithSingleAppExport(appInfo: AppInfo, exportDir: String) {
        // 显示文件名输入对话框
        fileNameInputDialog.showSingleAppFileNameDialog(appInfo) { customFileName ->
            // 显示导出进度对话框
            val progressDialog = createExportProgressDialog(1)
            progressDialog.show()

            lifecycleScope.launch {
                try {
                    val result = appExporter.exportApp(appInfo, exportDir, customFileName)

                    progressDialog.dismiss()
                    showExportResultDialog(result)

                } catch (e: Exception) {
                    progressDialog.dismiss()
                    Toast.makeText(this@MainActivity, "导出失败: ${e.message}", Toast.LENGTH_LONG).show()
                }
            }
        }
    }

    private fun uninstallSelectedApps() {
        val selectedApps = getAllSelectedApps()
        if (selectedApps.isEmpty()) {
            Toast.makeText(this, R.string.no_apps_selected_for_uninstall, Toast.LENGTH_SHORT).show()
            return
        }

        // 检查是否包含系统应用
        val systemApps = selectedApps.filter { it.isSystemApp }
        if (systemApps.isNotEmpty()) {
            Toast.makeText(this, R.string.uninstall_system_app_warning, Toast.LENGTH_SHORT).show()
            return
        }

        performUninstall(selectedApps)
    }

    private fun performUninstall(selectedApps: List<AppInfo>) {
        // 卸载第一个应用
        val firstApp = selectedApps.first()
        uninstallApp(firstApp.packageName)

        // 如果有多个应用，显示提示
        if (selectedApps.size > 1) {
            Toast.makeText(this, "请依次卸载选中的应用", Toast.LENGTH_SHORT).show()
        }
    }

    private fun uninstallApp(packageName: String) {
        try {
            val intent = Intent(Intent.ACTION_DELETE).apply {
                data = Uri.parse("package:$packageName")
                flags = Intent.FLAG_ACTIVITY_NEW_TASK
            }
            startActivity(intent)

            // 延迟刷新应用列表，给用户时间完成卸载操作
            Handler(Looper.getMainLooper()).postDelayed({
                loadApps()
                // 不再调用exitSelectionMode()，保持选择模式
            }, 3000) // 3秒后刷新列表

        } catch (e: Exception) {
            Toast.makeText(this, "${getString(R.string.uninstall_failed)}: ${e.message}", Toast.LENGTH_SHORT).show()
        }
    }


}